#include <avr/io.h>
#include <avr/interrupt.h>
#include <avr/eeprom.h>
#include <string.h>

#include "adc.h"
#include "tickcount.h"



volatile uint16_t local_current_measures[6];


struct ChrMeasuresStruct
{
unsigned short BatteryVoltage_V;
unsigned short ChargerCurrent_mA;
unsigned short ChargerSupplyVoltage_V;
unsigned short AVCC_Reference_V;
unsigned short uC_Supply_V;
} ChargerMeasures;


unsigned short AVCC_Reference_V;
uint16_t tc_LastAction;
unsigned char measures_from_intref;

uint16_t ui16_tmp[2];

void InitCharger(void)
{
	ChargerMeasures.BatteryVoltage_V=0;
	ChargerMeasures.ChargerCurrent_mA=0;
	ChargerMeasures.ChargerSupplyVoltage_V=0;
	ChargerMeasures.AVCC_Reference_V=0;
	ChargerMeasures.uC_Supply_V=0;

	AVCC_Reference_V=500; /* 5V */
	tc_LastAction=GetTickCount();
	AdcSwitchToInternalReference(1);
	measures_from_intref=1;
}




void ChargerProcess(void)
{
	if(GetTickSince(tc_LastAction)>100)
	{
		tc_LastAction=GetTickCount();
		if(GetMeasureData(local_current_measures, NULL))
		{
			if(measures_from_intref)
			{
				ChargerMeasures.AVCC_Reference_V=(uint16_t) (( ((uint32_t)local_current_measures[4])*100*256 )/102400 ); /* uref=2.56V=256, max scale at: 1024*/
				ChargerMeasures.AVCC_Reference_V*=2; /* it is divide on resistance by two*/
				AdcSwitchToInternalReference(0);
				measures_from_intref=0;

			} else
			{
				AdcSwitchToInternalReference(1);
				measures_from_intref=1;
				if(ChargerMeasures.AVCC_Reference_V>300)
				{

					ChargerMeasures.uC_Supply_V=(uint16_t) (( ((uint32_t)local_current_measures[4])*100*(uint32_t)ChargerMeasures.AVCC_Reference_V )/102400 ); /* max scale at: 1024*/
					ChargerMeasures.uC_Supply_V*=2; /* it is divide on resistance by two*/

					
					ui16_tmp[0]=(uint16_t) (( ((uint32_t)local_current_measures[0])*100*(uint32_t)ChargerMeasures.AVCC_Reference_V )/102400 ); /* max scale at: 1024*/
					ui16_tmp[1]=(uint16_t) (( ((uint32_t)local_current_measures[1])*100*(uint32_t)ChargerMeasures.AVCC_Reference_V )/102400 ); /* max scale at: 1024*/

					ChargerMeasures.ChargerSupplyVoltage_V=ui16_tmp[0];

					ChargerMeasures.ChargerCurrent_mA=(ui16_tmp[0]-ui16_tmp[1]); /* i=u/r where r=10 but we want to get result in mA then i=u*1000/10 ut the voltage is multiple by 100*/
					ChargerMeasures.BatteryVoltage_V=(( ((uint32_t)local_current_measures[2])*100*(uint32_t)ChargerMeasures.AVCC_Reference_V )/102400 ); /* max scale at: 1024*/
					ChargerMeasures.BatteryVoltage_V-=020; ; /* 020 = 0.20V - diode drop voltage */


				} else
				{
					/* something goes wrong */
					ChargerMeasures.BatteryVoltage_V=0;
					ChargerMeasures.ChargerCurrent_mA=0;
					ChargerMeasures.ChargerSupplyVoltage_V=0;
					ChargerMeasures.uC_Supply_V=0;
				}

			}

		}
	}

}


void GetChargerMeasures(char *packet, unsigned char *len)
{
	memcpy(packet,&ChargerMeasures,sizeof(ChargerMeasures));
	*len=sizeof(ChargerMeasures);
}


